package jwf.fcgi;

import java.io.IOException;
import java.io.InputStream;
import java.util.HashMap;
import java.util.Map;

public class FCGXParam {

    private Map<String, String> contentData;

    private String paddingData;

    public FCGXParam() {
	contentData = new HashMap<String, String>();
	paddingData = "";
    }

    public void addParam(String key, String value) {
	contentData.put(key, value);
    }

    public Map<String, String> getParams() {
	return contentData;
    }

    public String getPaddingData() {
	return paddingData;
    }

    public void setPaddingData(String paddingData) {
	this.paddingData = paddingData;
    }

    public static FCGXParam makeParams(InputStream in, FCGXHeader fcgxHeader)
	    throws IOException {
	FCGXParam param = new FCGXParam();
	int paramsLength = fcgxHeader.getContentLength();
	if (paramsLength != 0) {
	    byte[] buffer = new byte[paramsLength];
	    int l = in.read(buffer, 0, paramsLength);
	    if (l != paramsLength) {
		return param;
	    }
	    int pos = 0;
	    // get Name-Value Pair
	    for (; pos < paramsLength;) {
		int nameLength = 0;
		if ((buffer[pos] & 0x80) != 0) {
		    nameLength = ((buffer[pos++] & 0x7F) << 24)
			    + ((buffer[pos++] & 0xFF) << 16)
			    + ((buffer[pos++] & 0xFF) << 8)
			    + (buffer[pos++] & 0xFF);
		} else {
		    nameLength = (buffer[pos++] & 0xFF);
		}
		int valueLength = 0;
		if ((buffer[pos] & 0x80) != 0) {
		    valueLength = ((buffer[pos++] & 0x7F) << 24)
			    + ((buffer[pos++] & 0xFF) << 16)
			    + ((buffer[pos++] & 0xFF) << 8)
			    + (buffer[pos++] & 0xFF);
		} else {
		    valueLength = (buffer[pos++] & 0xFF);
		}
		String name = new String(buffer, pos, nameLength);
		pos += nameLength;
		String value = new String(buffer, pos, valueLength);
		pos += valueLength;
		param.addParam(name, value);
	    }
	}

	// get padding
	int pos = 0;
	int paddingLength = fcgxHeader.getPaddingLength();
	if (paddingLength != 0) {
	    byte[] buffer = new byte[fcgxHeader.paddingLength];
	    int l2 = in.read(buffer, 0, paddingLength);
	    if (l2 == paddingLength) {
		String paddingData = new String(buffer, pos, paddingLength);
		param.setPaddingData(paddingData);
		pos += paddingLength;
	    }
	}

	return param;
    }
}
